package com.sbc.auth.filter;

import com.sbc.auth.toolkit.JWTUtil;
import jakarta.servlet.*;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.springframework.util.StringUtils;

import java.io.IOException;

/**
 * @description: JWT 认证过滤器
 * @author: songbaicheng
 * @create: 2024-04-29 10:44
 **/
public class JwtAuthenticationFilter implements Filter {

    @Override
    public void init(jakarta.servlet.FilterConfig filterConfig) throws ServletException {
        jakarta.servlet.Filter.super.init(filterConfig);
    }

    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
        HttpServletRequest httpRequest = (HttpServletRequest) request;
        HttpServletResponse httpResponse = (HttpServletResponse) response;
        // 设置响应字符编码为 UTF-8
        httpResponse.setCharacterEncoding("UTF-8");

        String requestURI = httpRequest.getRequestURI();
        if (!requestURI.endsWith("/login") && !requestURI.endsWith("/register")) {
            // 获取请求头 Token
            String token = getJwtFromRequest(httpRequest);
            if (token == null) {
                // 如果没有携带 Token，返回 401 错误
                httpResponse.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
                httpResponse.getWriter().write("未携带 Token");
                return;
            }
            // 如果 Token 无效，也返回 401 错误
            if (!JWTUtil.validateToken(token)) {
                httpResponse.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
                httpResponse.getWriter().write("Token 已失效，请重新登录获取新 Token");
                return;
            }
        }

        chain.doFilter(request, response);
    }


    /**
     * 获取请求头 Token 凭证
     *
     * @param request 请求信息
     * @return Token 令牌
     */
    private String getJwtFromRequest(HttpServletRequest request) {
        String bearerToken = request.getHeader("Authorization");
        if (StringUtils.hasText(bearerToken) && bearerToken.startsWith("Bearer ")) {
            return bearerToken.substring(7);
        }
        return null;
    }
}
